﻿#region Header

/*
Remote views based on linq
By

Pascal Hauser 
Dipl. Ing. in Informatik, Hochschule für Technik Rapperswil, 2006
Master Thesis, Hochschule für Technik Rapperswil, 2008-2010

and

Raphael Gfeller
Dipl. Ing. in Informatik, Hochschule für Technik Rapperswil, 2006
Master Thesis, Hochschule für Technik Rapperswil, 2008-2010

*/

#endregion

#region Usings

using System;
using System.Collections;
using System.Collections.Generic;
using Sebarf.Services.Interfaces;
using Sebastof.Services.Interfaces;

#endregion

namespace Sebastof.Client.Services.Impl {
	/// <summary>
	/// Impl <see cref="IObservableCollectionCreatorService"/>
	/// </summary>
	public class ObservableCollectionCreatorService : Service, IObservableCollectionCreatorService {
		#region Public Properties

		[ServiceRequest]
		public IAppliedChangesOnObjectsCollectorService ObjectTrackerService { get; set; }

		#endregion

		#region Public Methods

		public ObservableCollectionCreatorService(IAppliedChangesOnObjectsCollectorService observer) {
			ObjectTrackerService = observer;
		}

		public ObservableCollectionCreatorService() {
		}

		#endregion

		#region IObservableCollectionCreatorService Members

		public object ConvertToObservableCollection(object collection, object parentObject, string parentObjectKey) {
			// list?
			if (collection is IList) {
				Type typeOfItem = collection.GetType();
				// generic?
				if (typeOfItem.IsGenericType) {
					// one generic argument?
					Type[] genericArguements = typeOfItem.GetGenericArguments();
					if (genericArguements.Length == 1) {
						Type genericType = genericArguements[0];

						// generate list type
						Type enumerableType = typeof(List<>).MakeGenericType(genericType);

						if (typeOfItem == enumerableType) {
							// found list<>
							Type observableListType = typeof(ObservableList<>).MakeGenericType(genericType);

							var observableList =
								(IList)Activator.CreateInstance(observableListType, ObjectTrackerService, parentObject, parentObjectKey);
							foreach (object entry in collection as IList) {
								observableList.Add(entry);
							}
							return observableList;
						}
					}
				}
			}
			return collection;
		}

		#endregion
	}
}